package com.project.springboot.shudu;

import java.util.HashSet;
import java.util.Set;

/**
 * description: 数独
 * @author 朱正磊
 * @date 2024-10-11 13:34:19
 */
public class Sudoku {

    private final int[][] board;

    public Sudoku() {
        board = new int[9][9];
    }

    // 检查行是否合法
    private boolean isRowValid(int row, int num) {
        Set<Integer> set = new HashSet<>();
        for (int i = 0; i < 9; i++) {
            if (board[row][i] != 0) {
                if (!set.add(board[row][i])) {
                    return false;
                }
            }
        }
        return !set.contains(num);
    }

    // 检查列是否合法
    private boolean isColumnValid(int col, int num) {
        Set<Integer> set = new HashSet<>();
        for (int i = 0; i < 9; i++) {
            if (board[i][col] != 0) {
                if (!set.add(board[i][col])) {
                    return false;
                }
            }
        }
        return !set.contains(num);
    }

    // 检查 3x3 子区域是否合法
    private boolean isSubgridValid(int startRow, int startCol, int num) {
        Set<Integer> set = new HashSet<>();
        for (int i = startRow; i < startRow + 3; i++) {
            for (int j = startCol; j < startCol + 3; j++) {
                if (board[i][j] != 0) {
                    if (!set.add(board[i][j])) {
                        return false;
                    }
                }
            }
        }
        return !set.contains(num);
    }

    // 检查整个数独是否合法
    private boolean isBoardValid(int row, int col, int num) {
        return isRowValid(row, num) && isColumnValid(col, num)
                && isSubgridValid(row - row % 3, col - col % 3, num);
    }

    // 放置数字
    public boolean placeNumber(int row, int col, int num) {
        if (isBoardValid(row, col, num)) {
            board[row][col] = num;
            return true;
        }
        return false;
    }

    // 打印数独
    public void printBoard() {
        for (int i = 0; i < 9; i++) {
            for (int j = 0; j < 9; j++) {
                System.out.print(board[i][j] + " ");
            }
            System.out.println();
        }
    }

}
